/*
 * @Author: fanjs
 * @Date: 2025-03-16 01:26:27
 * @Description: 收件人
 */

import { useState, useMemo, useEffect, useCallback } from 'react';
import { addToast, useDisclosure, Button, Modal, ModalContent, ModalHeader, ModalBody, ModalFooter, Pagination, Spinner, Tooltip, Input, Chip } from '@heroui/react';
import { SvgIcon } from '@/components/SvgIcon'
import Upload from './components/Upload'
import ResultTable from './components/ResultTable'
import { sendEmailApi, fetchRecipientListAllApi, fetchTaskApi, verifyStatusApi, reconnectApi } from '@/service/api/email'
import { useParams } from 'react-router-dom'
import { localStg } from '@/utils/storage';

const EmailRecipients: React.FC = (() => {
  const { task_id } = useParams<{ task_id: string }>();

  const { isOpen: isUploadOpen, onOpenChange: onUploadOpenChange } = useDisclosure();
  const { isOpen: isReconnectOpen, onOpenChange: onReconnectOpenChange } = useDisclosure();
  const { isOpen: isResultOpen, onOpenChange: onResultOpenChange } = useDisclosure();

  const [isSendLoading, setIsSendLoading] = useState(false)
  const [isReconnectLoading, setIsReconnectLoading] = useState(false)
  const [isPageLoading, setIsPageLoading] = useState(true);

  const [isPassed, setIsPassed] = useState(false) // 发送是否完成
  const [list, setList] = useState<any>([])

  const [resultData, setResultData] = useState<any>({})
  const [taskInfo, setTaskInfo] = useState<any>({})

  // 表格列名称 -> 根据所需变量信息设置
  const [columnsIsDisabled, setColumnsIsDisabled] = useState(false)
  const [columns, setColumns] = useState<any>({
    '邮箱地址': '邮箱地址' // 必填
  })
  const [variables, setVariables] = useState<string[]>([])

  // 分页
  const rowsPerPage = 20;
  const [page, setPage] = useState(1);
  const pages = Math.ceil(list.length / rowsPerPage);
  const tableList = useMemo(() => {
    const start = (page - 1) * rowsPerPage;
    const end = start + rowsPerPage;
    return list.slice(start, end);
  }, [page, list, rowsPerPage]);

  // 上传准备
  const [uploadParams, setUploadParams] = useState<any>({})
  const onReadyUpload = useCallback(() => {
    const data: any = {
      task_id,
      columns: JSON.stringify(columns),
    }
    setUploadParams(data)
    onUploadOpenChange()
  }, [columns, task_id, onUploadOpenChange]);

  // 上传完成
  const onSuccess = (response: any) => {
    if (Array.isArray(response)) {
      setList([...response, ...list])
    } else {
      const { list: newList } = response
      setList([...newList, ...list])
    }
    setTimeout(() => {
      fetchTaskInfo()
      onUploadOpenChange()
    }, 700);
  }

  // 检查邮箱连接状态
  const checkLinkStatus = useCallback(async () => {
    const { data }: any = await verifyStatusApi();
    if (!data || !data.connecting) {
      onReconnectOpenChange()
      return false
    }
    return true
  }, [onReconnectOpenChange]);

  // 如果存在 taskInfo.columns 则将 columns 设置为 taskInfo.columns
  // 并且禁止修改
  useEffect(() => {
    if (taskInfo.columns) {
      setColumns(JSON.parse(taskInfo.columns))
      setColumnsIsDisabled(true)
    }
  }, [taskInfo])

  // 获取当前任务下收件人列表
  const fetchList = useCallback(async () => {
    setIsPageLoading(true);
    try {
      const { data } = await fetchRecipientListAllApi(task_id as string);
      if (data) setList(data)
    } catch {
      addToast({ title: '获取列表失败' })
    } finally {
      setTimeout(() => setIsPageLoading(false), 300);
    }
  }, [task_id]);

  // 发送
  const handleSend = useCallback(async () => {
    setIsSendLoading(true)
    try {
      // 校验连接状态
      const isConnected = await checkLinkStatus()
      if (!isConnected) return

      const { data } = await sendEmailApi(task_id as string, { email_id: localStg.get('email_id') })
      if (!data) return setIsPassed(false)
      setIsPassed(true)
      setResultData(data)
      onResultOpenChange()
      setTimeout(() => fetchList(), 700)
    } finally {
      setTimeout(() => setIsSendLoading(false), 700);
    }
  }, [task_id, checkLinkStatus, fetchList, onResultOpenChange]);

  // 重新连接邮箱
  const onReconnect = useCallback(async () => {
    setIsReconnectLoading(true)
    try {
      const email_id = localStg.get('email_id')
      if (!email_id) return addToast({ title: '邮箱配置不存在，请重新配置' })
      const { data: eid }: any = await reconnectApi(email_id)
      if (!eid) return
      onReconnectOpenChange()
      localStg.set('email_id', eid)
      addToast({ title: '邮箱服务已重新连接, 继续发送邮件', color: 'secondary' })
      handleSend()
    } finally {
      setTimeout(() => setIsReconnectLoading(false), 700);
    }
  }, [onReconnectOpenChange, handleSend]);

  // 获取任务信息
  const fetchTaskInfo = useCallback(async () => {
    const { data } = await fetchTaskApi(task_id as string);
    if (data) {
      setTaskInfo(data)
      setVariables(data.variables)
      data.variables.forEach((item: any) => {
        setColumns((prev: any) => ({ ...prev, [item]: item }))
      })
    }
  }, [task_id]);

  const refresh = useCallback(() => {
    fetchTaskInfo()
    fetchList()
  }, [fetchTaskInfo, fetchList]);

  useEffect(() => {
    refresh();
  }, [refresh]);

  // 顶部筛选
  const topContent = useMemo(() => {
    return (
      <div className="flex flex-col">
        <div className="flex justify-between gap-3 font-medium" >
          <h3 className="text-md flex-y-center">
            {/* <SvgIcon icon="line-md:account" className='text-xl mr-1' /> */}
            配置收件人信息 （邮件中用到的变量：{variables.map((item: any) => item).join('、')}）
          </h3>
          <div className="flex gap-3">
            {/* <Button color="secondary" endContent={<SvgIcon icon="line-md:email-plus" className="text-base" />}>
              录入新增
            </Button> */}
            <Button color="secondary" variant="flat" onPress={onReadyUpload} endContent={<SvgIcon icon="line-md:uploading-loop" className="text-base" />}>
              文档上传
            </Button>
            {/* 按钮 */}
            <Button isDisabled={isPassed || isSendLoading} color='secondary' onPress={handleSend}>
              {isSendLoading && <SvgIcon className='text-4' icon="line-md:loading-twotone-loop" />}
              {isPassed && !isSendLoading && <SvgIcon icon="line-md:check-all" />}
              {isSendLoading ? '发送中...' : isPassed ? '发送完成' : '开始发送'}
            </Button>
            {/* {!isPassed && <Button color="secondary" onPress={toTaskRecord}>去查看邮件</Button>} */}
          </div>
        </div>

        {/* 文档列名称设置 */}
        <div className=" w-full mt-3 flex-y-center">
          <Tooltip content={
            <div className="px-1 py-2">
              <div className="text-small font-bold">设置文档中表头的列名</div>
              <div className="text-tiny mt-2">默认值：邮箱地址、{variables.map((item: any) => item).join('、')}</div>
              <div className="text-tiny mt-2">如果文档中与默认值一致，将输入框留空</div>
              <div className="text-tiny mt-2">如果文档中的某一列与默认值不同，按文档中的对应名称填写</div>
              <div className="text-tiny mt-2">上传收件人数据成功后，列名将不可修改</div>
            </div>
          } placement="bottom">
            <SvgIcon icon="line-md:question-circle" className='text-2xl mr-3' />
          </Tooltip>
          <div className="flex flex-1 gap-2">
            <Input value={columns['邮箱地址']} isDisabled={columnsIsDisabled} onValueChange={(value) => setColumns((prev: any) => ({ ...prev, '邮箱地址': value }))} placeholder="设置邮箱地址列名（默认：邮箱地址）" />
            {variables.map((item: any) => (
              <Input placeholder={`设置${item}列名（默认：${item}）`} isDisabled={columnsIsDisabled} value={columns[item]} onValueChange={(value) => setColumns((prev: any) => ({ ...prev, [item]: value }))} />
            ))}
          </div>
        </div>
      </div>
    );
  }, [columns, variables, isPassed, isSendLoading, handleSend, onReadyUpload, columnsIsDisabled]);

  // 底部分页
  const bottomContent = useMemo(() => {
    return (
      <div className="py-0 pr-2 flex justify-end items-center">
        <div className='text-default-500 dark:text-white/70 text-[13px] mr-4 flex-y-center gap-3'>
          <span>
            共计 <span className='text-secondary font-bold'>{taskInfo.total_count}</span> 条数据
          </span>
          <div>|</div>
          <span>
            已发送 <span className='text-secondary font-bold'>{taskInfo.sent_count}</span> 条
          </span>
          <div>|</div>
          <span>
            未发或失败 <span className='text-danger font-bold'>{taskInfo.failed_count}</span> 条
          </span>
        </div>
        <Pagination
          size="sm"
          isCompact
          showControls
          showShadow
          color="secondary"
          page={page}
          total={pages}
          onChange={setPage}
        />
      </div>
    );
  }, [page, pages, taskInfo]);

  return (
    <div className='p-4 relative'>
      {isPageLoading && (
        <div className="absolute top-0 left-0 w-full h-[calc(100vh-56px)] z-50 bg-default-100/50 flex justify-center items-center ">
          <Spinner size="lg" color="secondary" />
        </div>
      )}

      <ResultTable
        list={tableList}
        topContent={topContent}
        bottomContent={bottomContent}
        columns={columns}
        refetch={refresh}
      />

      {/* 上传 */}
      <Modal isOpen={isUploadOpen} onOpenChange={onUploadOpenChange}>
        <ModalContent>
          {(onClose) => (
            <>
              <ModalHeader className="flex flex-col gap-1">上传收件人信息</ModalHeader>
              <ModalBody>
                <Upload data={uploadParams} onSuccess={onSuccess} />
              </ModalBody>
              <ModalFooter className='flex-center'>
                <Button size='sm' variant='flat' color="secondary" onPress={onClose}>
                  关 闭
                </Button>
              </ModalFooter>
            </>
          )}
        </ModalContent>
      </Modal>

      {/* 拦截弹窗 */}
      <Modal
        isDismissable={false}
        isKeyboardDismissDisabled={true}
        isOpen={isReconnectOpen}
        onOpenChange={onReconnectOpenChange}
      >
        <ModalContent>
          {(onClose) => (
            <>
              <ModalHeader className="flex flex-col gap-1">邮箱连接已断开</ModalHeader>
              <ModalBody>需要重新连接邮箱吗？</ModalBody>
              <ModalFooter className='gap-x-4'>
                <Button color="default" variant="flat" onPress={onClose}>取消</Button>
                <Button color="secondary" isLoading={isReconnectLoading} onPress={onReconnect}>重连</Button>
              </ModalFooter>
            </>
          )}
        </ModalContent>
      </Modal>

      {/* 发送结果 */}
      <Modal backdrop="blur" isOpen={isResultOpen} size='xs' classNames={{
        header: 'p-4',
        body: 'p-4',
        footer: 'px-4 pt-0 pb-4',
      }} onClose={onResultOpenChange}>
        <ModalContent>
          <ModalHeader>发送完成</ModalHeader>
          <ModalBody>
            <p className='-mt-2 pl-2 font-medium text-center'>
              本次共计发送
              <span className='text-secondary mx-2 font-bold'>{resultData.send_total_count || 0}</span>
              封邮件
            </p>
            <div className='flex flex-col gap-2 items-center pb-4'>
              <Chip color="secondary" variant="solid" size='lg' radius='sm'>
                成功发送 - <span className='font-bold'>{resultData.sent_count || 0} 封</span>
              </Chip>
              <Chip color="danger" variant="solid" size='lg' radius='sm'>
                发送失败 - <span className='font-bold'>{resultData.failed_count || 0} 封</span>
              </Chip>
            </div>
          </ModalBody>
          <ModalFooter className='flex-center'>
            <Button color="secondary" className='w-full' variant="flat" onPress={onResultOpenChange}>
              返 回
            </Button>
          </ModalFooter>
        </ModalContent>
      </Modal>
    </div>
  )
});

export default EmailRecipients;
